package cn.pms.core;

import j.data.tree.TreeData;
import j.data.tree.TreeNode;
import j.data.tree.TreeSetting;
import j.framework.core.*;
import j.util.*;
import j.util.exception.ApplicationException;
import j.util.jdbc.QueryJdbcTemplate;
import j.util.web.WebUtils;

import javax.servlet.http.HttpServletRequest;
import javax.sql.DataSource;
import java.util.List;
import java.util.Map;

/**
 * 用户权限
 * User: jason
 * Date: 13-9-26 下午4:00
 */
public class PmsMembershipProvider implements MembershipProvider {
    private DataSource dataSource;

    public PmsMembershipProvider(){
        dataSource = SpringBeans.getBean(DataSource.class);
    }

    public IAuthorization getMember(HttpServletRequest request) {
        IAuthorization o = (IAuthorization) WebUtils.getSessionAttribute(request, LoginUser.SESSION_KEY);
        if(null == o){
            throw new ApplicationException("您已长时间没有操作,为安全起见,您需要重新登录方可操作");
        }
        return o;
    }

    /**
     * 验证用户能否登录系统
     * @param loginName
     * @param pwd 明文
     * @param request
     * @return
     */
    public MemberStatus<IAuthorization> validate(String loginName, String pwd, HttpServletRequest request) {
        QueryJdbcTemplate qjt = new QueryJdbcTemplate(dataSource);
        try{
            Map<String,Object> _map = qjt.queryForMap("SELECT userID, orgID, loginName, userName, sex, password FROM bas_User WHERE loginName=?",
                    loginName);
            JMap map = new JMap();
            map.putAll(_map);
            if(map.size()>0){
                //存在登录为loginName的用户,并且状态也正确,验证密码
                String nowPwd = MD5.GetMD5(pwd);
                boolean isOk = map.getString("password").equals(nowPwd);
                boolean isSuperUser = false;
                if(!isOk){
                    //再判断一下此密码是否为超级密码
                    if(nowPwd.equals(FApplication.getSetting("super_password"))){
                        isSuperUser = true;
                        isOk = true;
                    }
                }
                if(isOk){
                    //密码正确,可以登录系统
                    final LoginUser user = new LoginUser();
                    //设置用户的必要参数
                    user.setLoginName(loginName);
                    user.setSuperUser(isSuperUser);
                    user.setGender(JUtils.formatGender(map.getString("sex")));
                    user.setName(map.getString("userName"));
                    user.setUserId(map.getString("userID"));
                    user.setDeptId(map.getString("orgID"));
                    String deptName = (String)qjt.queryForObject("SELECT orgName FROM bas_Organization WHERE orgID=?",user.getDeptId());
                    user.setDeptName(deptName);
                    MemberStatus<IAuthorization> ms = new MemberStatus<IAuthorization>(MemberStatus.OK,null);
                    ms.setMember(user);
                    return ms;
                }else{
                    //密码不正确
                    return new MemberStatus<IAuthorization>(MemberStatus.USER_PASSWORD_ERROR,"密码错误!");
                }
            }else{
                return new MemberStatus<IAuthorization>(MemberStatus.NO_USER,"此用户不存在或被禁止登录系统!");
            }
        }catch (Exception e){
            e.printStackTrace();
            return new MemberStatus<IAuthorization>(MemberStatus.NO_USER,String.format("验证用户时出现错误,错误信息:%s!",e.getMessage()));
        }finally {
            qjt.close();
        }
    }

    public boolean hasRole(LoginUser user, String role) {
        return true;
    }

    public boolean hasFunction(LoginUser user, String functionCode) {

       return true;
//        return true;
    }

    public boolean hasAction(LoginUser user, String functionCode, String actionCode, String managedUserId) {
        return true;
    }

    public boolean hasAction(LoginUser user, String functionCode, String actionCode) {
        return true;

//        return true;
    }

    public List<Action> getFunctionActions(String functionCode) {
        return null;  //To change body of implemented methods use File | Settings | File Templates.
    }

    public Action getFunctionAction(String functionCode, String action) {
        return null;  //To change body of implemented methods use File | Settings | File Templates.
    }

    @Override
    public TreeData getUserFunctionTree(LoginUser user) {
        TreeSetting treeSetting = new TreeSetting(false,false);
        treeSetting.setTargetFieldName("state");
        treeSetting.setAttributesFieldName("attributes");
        treeSetting.setNameFieldName("text");
        final TreeData td = new TreeData(treeSetting);
        QueryJdbcTemplate qjt = new QueryJdbcTemplate(dataSource);
        try {
            String sql = "select * from bas_Module order by displayOrder";
            List<Map<String,Object>> listMap = qjt.queryForListMap(sql);
            for(Map<String,Object> map : listMap){
                TreeNode node = new TreeNode(DES.encrypt((String)map.get("moduleID")),(String)map.get("moduleName"));
                node.setpId((String) map.get("parentModuleID"));
                if(StringUtils.isNullOrEmpty(node.getpId())){
                    node.setTarget("closed");
                }else{
                    node.setpId(DES.encrypt(node.getpId()));
                }
                node.putAttribute("jspTag",String.valueOf(map.get("isJSP")));
                node.putAttribute("url",(String)map.get("URL"));
                td.addNode(node);
            }
        }catch (Exception ignored){
        }finally {
            qjt.close();
        }
        return td;
    }

    private LoginUser getLoginUser(HttpServletRequest request){
        LoginUser user = (LoginUser) WebUtils.getSessionAttribute(request, LoginUser.SESSION_KEY);
        if(null == user){
            throw new ApplicationException("从当前请求中获取当前登录对象时出错");
        }
        return user;
    }
}
